package de.mrapp.tabswitcher.iterator;

import de.mrapp.tabswitcher.TabSwitcher;
import de.mrapp.tabswitcher.model.AbstractItem;
import de.mrapp.tabswitcher.model.AddTabItem;
import de.mrapp.tabswitcher.model.Model;
import de.mrapp.tabswitcher.model.TabItem;
import de.mrapp.util.Condition;
import de.mrapp.ohos_util.view.AttachedViewRecycler;

public class ItemIterator extends AbstractItemIterator {
    /**
     * A builder, which allows to configure and create instances of the class {@link ItemIterator}.
     */
    public static class Builder extends AbstractBuilder<Builder, ItemIterator> {

        /**
         * The model, which belongs to the tab switcher, whose items should be iterated by the
         * iterator, which is created by the builder.
         */
        private final Model model;

        /**
         * The view recycler, which allows to inflate the views, which are used to visualize the
         * items, which are iterated by the iterator, which is created by the builder.
         */
        private final AttachedViewRecycler<AbstractItem, ?> viewRecycler;

        /**
         * Creates a new builder, which allows to configure and create instances of the class {@link
         * ItemIterator}.
         *
         * @param model
         *         The model, which belongs to the tab switcher, whose items should be iterated by
         *         the iterator, which is created by the builder, as an instance of the type {@link
         *         Model}. The model may not be null
         * @param viewRecycler
         *         The view recycler, which allows to inflate the views, which are used to visualize
         *         the items, which are iterated by the iterator, which is created by the builder,
         *         as an instance of the class AttachedViewRecycler. The view recycler may not be
         *         null
         */
        public Builder( final Model model,
                        final AttachedViewRecycler<AbstractItem, ?> viewRecycler) {
            Condition.INSTANCE.ensureNotNull(model, "The model may not be null");
            Condition.INSTANCE.ensureNotNull(viewRecycler, "The view recycler may not be null");
            this.model = model;
            this.viewRecycler = viewRecycler;
        }

        
        @Override
        public ItemIterator create() {
            return new ItemIterator(model, viewRecycler, reverse, start);
        }

    }

    /**
     * The model, which belongs to the tab switcher, whose tabs are iterated.
     */
    private final Model model;

    /**
     * The view recycler, which allows to inflated the views, which are used to visualize the
     * iterated items.
     */
    private final AttachedViewRecycler<AbstractItem, ?> viewRecycler;

    /**
     * Creates a new iterator, which allows to iterate the items, which correspond to the child
     * views of a {@link TabSwitcher}.
     *
     * @param model
     *         The model, which belongs to the tab switcher, whose items should be iterated, as an
     *         instance of the type {@link Model}. The model may not be null
     * @param viewRecycler
     *         The view recycler, which allows to inflate the views, which are used to visualize the
     *         iterated items, as an instance of the class AttachedViewRecycler. The view recycler
     *         may not be null
     * @param reverse
     *         True, if the items should be iterated in reverse order, false otherwise
     * @param start
     *         The index of the first item, which should be iterated, as an {@link Integer} value or
     *         -1, if all items should be iterated
     */
    private ItemIterator( final Model model,
                          final AttachedViewRecycler<AbstractItem, ?> viewRecycler,
                         final boolean reverse, final int start) {
        Condition.INSTANCE.ensureNotNull(model, "The model may not be null");
        Condition.INSTANCE.ensureNotNull(viewRecycler, "The view recycler may not be null");
        this.model = model;
        this.viewRecycler = viewRecycler;
        initialize(reverse, start);
    }

    @Override
    public final int getCount() {
        return model.getCount() + (model.isAddTabButtonShown() ? 1 : 0);
    }

    
    @Override
    public final AbstractItem getItem(final int index) {
        if (index == 0 && model.isAddTabButtonShown()) {
            return AddTabItem.create(viewRecycler);
        } else {
            return TabItem
                    .create(model, viewRecycler, index - (model.isAddTabButtonShown() ? 1 : 0));
        }
    }
}
